/*
 ------------------------------------------------------------------------------
 Copyright (C) 2006-2007 Team Blur.

 This file is part of the Quantum Engine source code.

 The Quantum Engine source code is free software; you can redistribute it and/or
 modify it under the terms of the GNU General Public License as published by
 the Free Software Foundation; either version 2 of the License, or (at your
 option) any later version.

 The Quantum Engine source code is distributed in the hope that it will be useful,
 but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
 or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License for
 more details.

 You should have received a copy of the GNU General Public License along with
 the Quantum Engine source code; if not, write to the Free Software Foundation, Inc.,
 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
 ------------------------------------------------------------------------------
*/


#ifndef __CM_PUBLIC_H__
#define __CM_PUBLIC_H__


// Loads and prepares the given map for collision detection
void			CM_LoadMap (const char *name);

// Frees the current map and all the models
void			CM_FreeMap (void);

// Loads and registers the given model
clipModel_t *	CM_RegisterModel (const char *name);

// Sets up a box model for collision detection
clipModel_t *	CM_SetupBoxModel (const odBounds &bounds, int surfaceFlags, int contentFlags);

// Creates a new instance of the given model, or returns an existing one.
// This must be used when doing collision detection on a dynamic model, because
// the clip model must be reconstructed every frame to match the animated
// geometry for every entity using the given model.
// The joints parameter can be NULL, in which case the model will be
// instantiated in its default pose.
clipModel_t *	CM_InstantiateDynamicModel (clipModel_t *model, int entityNum, odJointMat *joints);

// This should be called once per frame to release all the memory used by
// previous dynamic model instantiations
void			CM_ClearDynamicModelInstances (void);

// Returns the contents of all the brushes and surfaces of the given model
// OR'ed together
int				CM_GetModelContents (clipModel_t *model);

// Returns the bounds of the given model
void			CM_GetModelBounds (clipModel_t *model, odBounds &bounds);

// Returns the contents of the world or model volumes contacted by the given
// point (bounds == 0) or box (bounds != 0), or 0 if in empty space
int				CM_Contents (const odVec3 &point, const odBounds &bounds, int contentMask, clipModel_t *model, const odVec3 &modelOrigin, const odMat3 &modelAxis);

// Performs a point (bounds == 0) or box (bounds != 0) trace through the world
// or a model.
// A trace with start == end will actually perform a position test.
trace_t			CM_Trace (const odVec3 &start, const odVec3 &end, const odBounds &bounds, int contentMask, clipModel_t *model, const odVec3 &modelOrigin, const odMat3 &modelAxis);

// Returns the leaf contacted by the given point
int				CM_PointInLeaf (const odVec3 &point);

// Returns the cluster of the given leaf
int				CM_LeafCluster (int leafNum);

// Returns the area of the given leaf
int				CM_LeafArea (int leafNum);

// Returns true if a portal sky can be seen from the given leaf
bool			CM_LeafCanSeePortalSky (int leafNum);

// Returns the PVS for the given cluster
const byte *	CM_ClusterPVS (int clusterNum);

// Returns true if point is in the PVS of the given cluster.
// Also considers area connections.
bool			CM_PointInPVS (const odVec3 &point, int clusterNum, int areaNum);

// Returns true if bounds are in the PVS of the given cluster.
// Also considers area connections.
bool			CM_BoundsInPVS (const odBounds &bounds, int clusterNum, int areaNum);

// Returns the number of portals in the current map
int				CM_NumPortals (void);

// Returns the portal contacted by the given bounds, or -1 if no portal is
// contacted
int				CM_FindPortal (const odBounds &bounds);

// Sets the state of the given portal
void			CM_SetPortalState (int portalNum, bool open);

// Gets the state of the given portal
bool			CM_GetPortalState (int portalNum);

// Writes a bit vector of all the portals that are in an opened state.
// Returns the number of bytes needed to hold all the bits.
int				CM_WritePortalBits (byte *buffer);

// Returns true if the given areas are connected
bool			CM_AreasAreConnected (int areaNum1, int areaNum2);

// Returns the number of areas in the current map
int				CM_NumAreas (void);

// Returns the area contacted by the given point
int				CM_PointInArea (const odVec3 &point);

// Fills a list of all the areas contacted by the given bounds.
// Returns the number of areas in the list.
int				CM_BoundsInAreas (const odBounds &bounds, int *areas, int maxAreas);

// Returns the number of portals in the given area
int				CM_NumPortalsInArea (int areaNum);

// Returns a portal from the given area
void			CM_GetPortalFromArea (int areaNum, int portalNum, areaPortal_t *areaPortal);

// Writes a bit vector of all the areas that are in the same flood as the
// area parameter.
// Returns the number of bytes needed to hold all the bits.
int				CM_WriteAreaBits (int areaNum, byte *buffer);

// Statistics for debugging and optimization
void			CM_PrintStats (void);

// Initializes the collision subsystem
void			CM_Init (void);

// Shuts down the collision subsystem
void			CM_Shutdown (void);


#endif	// __CM_PUBLIC_H__
